home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
ftp.mactech.com 2010
/
ftp.mactech.com.tar
/
ftp.mactech.com
/
machack
/
Hacks96
/
FlyPaper.sit
/
Fly Paper
/
FlyPaper Source
/
App Sources
/
Clippings.cpp
next >
Wrap
Text File
|
1996-06-22
|
12KB
|
480 lines
#if 0
#include "ST_MacClasses.h"
#ifndef CLIPPINGS_H
#include "Clippings.h"
#endif
#ifndef FLYPAPERUTILS_H
#include "FlyPaperUtils.h"
#endif
#ifndef FLYPAPERAPP_H
#include "FlyPaperApp.h"
#endif
#ifndef FLYPAPERDRAGUTILS_H
#include "FlyPaperDragUtils.h"
#endif
#ifndef CLIPPINGFILE_H
#include "ClippingFile.h"
#endif
#ifndef THUMBNAIL_H
#include "Thumbnail.h"
#endif
#include <drag.h>
#include <Devices.h>
#include <Folders.h>
#include <TextUtils.h>
#include <Fonts.h>
#include "floaters.h"
extern GlobalsRec glob;
#define kWatchFolderDelay 60
WindowPtr gWindowBeingDragged = nil;
Point gClickPoint;
WindowPtr CreateClippingWindow (ClippingID id, Rect& bounds, Boolean onLeft);
typedef struct {
ClippingID clippingID;
Rect windowBounds;
WindowPtr window;
CThumbnail* thumbnail;
Boolean onLeft;
} ClippingRec;
typedef struct {
short numClippings;
unsigned long clippingsFolderDate;
short update;
ClippingRec clippings [];
} ClippingsListHeader, **ClippingListHandle;
ClippingListHandle gClippingsList = nil;
Boolean InitClippings ()
{
OSErr error;
gClippingsList = (ClippingListHandle) TempNewHandle (sizeof (ClippingsListHeader), &error);
if (!gClippingsList)
return false;
(**gClippingsList).numClippings = 0;
(**gClippingsList).update = 0;
(**gClippingsList).clippingsFolderDate = 1; // even less likely than 12:00am Jan 1, 1904
return true;
}
static
void CalcWindowPosition (Point dropPoint, Rect& bounds, short tile, Boolean &onLeft)
{
#define kClippingWidth 110
Rect globalRect = (**GetGrayRgn ()).rgnBBox;
OffsetRect (&bounds, 0, dropPoint.v + tile * 20);
if (globalRect.right - dropPoint.h < dropPoint.h - globalRect.left) {
onLeft = true;
OffsetRect (&bounds, globalRect.right - bounds.right - bounds.left, 0);
} else {
onLeft = false;
OffsetRect (&bounds, globalRect.left, 0);
}
}
static
short FindClipping (ClippingID id, ClippingRec& clipping)
{
for (short whichClipping = 0; whichClipping < (**gClippingsList).numClippings; ++whichClipping) {
if ((**gClippingsList).clippings [whichClipping].clippingID == id) {
clipping = (**gClippingsList).clippings [whichClipping];
return whichClipping;
}
}
return -1;
}
static
void DeleteClipping (ClippingID id)
{
for (short whichClipping = 0; whichClipping < (**gClippingsList).numClippings; ++whichClipping) {
if ((**gClippingsList).clippings [whichClipping].clippingID == id) {
delete (**gClippingsList).clippings [whichClipping].thumbnail;
BlockMoveData ( &(**gClippingsList).clippings [whichClipping + 1],
&(**gClippingsList).clippings [whichClipping],
sizeof (ClippingRec) * ((**gClippingsList).numClippings - whichClipping - 1));
SetHandleSize ((Handle) gClippingsList,
GetHandleSize ((Handle) gClippingsList) - sizeof (ClippingRec));
--(**gClippingsList).numClippings;
return;
}
}
}
static
void AppendClipping (ClippingRec& clipping)
{
if (PtrAndHand (&clipping, (Handle) gClippingsList, sizeof (ClippingRec)))
return;
else {
++(**gClippingsList).update;
++(**gClippingsList).numClippings;
}
}
void ProcessPendingClippings (void)
{
if ((**gClippingsList).update == 0)
return;
for (short whichClipping = 0; (**gClippingsList).update && (whichClipping < (**gClippingsList).numClippings); ++whichClipping) {
if ((**gClippingsList).clippings [whichClipping].window == nil) {
// create clipping window here
Rect bounds = (**gClippingsList).clippings [whichClipping].windowBounds;
Boolean onLeft = (**gClippingsList).clippings [whichClipping].onLeft;
ClippingID id = (**gClippingsList).clippings [whichClipping].clippingID;
(**gClippingsList).clippings [whichClipping].window =
CreateClippingWindow (id, bounds, onLeft);
--(**gClippingsList).update;
}
}
}
void CheckForNewClippings (void)
{
static unsigned long nextCheck = 0;
CInfoPBRec pb;
Str255 name;
long dirID;
if (TickCount () < nextCheck)
return;
nextCheck = TickCount () + kWatchFolderDelay;
OSErr error = FlyPaperFindFolder (kOnSystemDisk, kClippingsFolder, true, &pb.hFileInfo.ioVRefNum,
&dirID);
if (error)
return;
pb.hFileInfo.ioNamePtr = name;
pb.hFileInfo.ioFDirIndex = -1;
pb.hFileInfo.ioDirID = dirID;
error = PBGetCatInfoSync (&pb);
if (error)
return;
if (pb.dirInfo.ioDrMdDat != (**gClippingsList).clippingsFolderDate) {
(**gClippingsList).clippingsFolderDate = pb.dirInfo.ioDrMdDat;
for (pb.hFileInfo.ioFDirIndex = 1; ; ++pb.hFileInfo.ioFDirIndex) {
pb.hFileInfo.ioDirID = dirID;
if (PBGetCatInfoSync (&pb))
break;
if (pb.hFileInfo.ioFlFndrInfo.fdType != kClippingFileType)
continue;
ClippingID id;
ClippingRec clipping;
StringToNum (name, (long*) &id);
short index = FindClipping (id, clipping);
if (index < 0) {
FlyPaperAuxDataHandle auxData;
if (GetClippingFileAuxData (id, auxData))
return;
clipping.clippingID = id;
clipping.thumbnail = CThumbnail::NewThumbnail (id);
if (clipping.thumbnail)
clipping.thumbnail -> GetWindowBounds (clipping.windowBounds);
else
SetRect (&clipping.windowBounds, 0, 0, 40, 20);
CalcWindowPosition ((**auxData).dropSpot, clipping.windowBounds, 0, clipping.onLeft);
clipping.window = nil;
DisposeHandle ((Handle) auxData);
AppendClipping (clipping);
}
}
}
}
static
Boolean RememberDragItem (DragReference dragRef, ItemReference dragItem, ClippingID& clippingID, Point dropSpot)
{
short clippingResFile = -1;
FlyPaperAuxDataHandle auxData;
unsigned short numFlavors;
if (CountDragItemFlavors (dragRef, dragItem, &numFlavors))
return false;
for (unsigned short whichFlavor = 1; whichFlavor <= numFlavors; ++whichFlavor) {
if (AcceptableFlavor (dragRef, dragItem, whichFlavor)) {
FlavorType type;
FlavorFlags flags;
Size size;
if (GetFlavorType (dragRef, dragItem, whichFlavor, &type))
return false;
if (GetFlavorFlags (dragRef, dragItem, type, &flags))
return false;
if (clippingResFile == -1) {
if (CreateClippingFile (&clippingResFile, kClippingFileType, auxData, clippingID))
return false;
(**auxData).dropSpot = dropSpot;
}
ST_ResFileCloser clippingResFileCloser (clippingResFile);
Handle dataHandle = NULL;
if (GetFlavorDataSize (dragRef, dragItem, type, &size)) {
continue;
}
/* allocate memory for the drag item */
Handle data = NewHandle (size);
if (!data) {
OSErr error;
data = TempNewHandle (size, &error);
if (!data)
continue;
}
ST_Handle dataKiller (dataHandle);
{
ST_HandleStateSaver dataStateSaver (data);
HLock (data);
if (GetFlavorData (dragRef, dragItem, type, *data, &size, 0))
continue;
}
if (AddFlavorToClippingFile (clippingResFile, type, data))
continue;
WriteResource (data);
ReleaseResource (data);
dataKiller.Forget ();
clippingResFileCloser.Forget ();
}
}
if (clippingResFile != -1) {
CloseResFile (clippingResFile);
return true;
} else
return false;
}
void AcceptNewClipping (DragReference dragRef, Point dropLocation)
{
unsigned short numItems;
Boolean newClippingMade = false;
short tileCount = 0;
if (CountDragItems (dragRef, &numItems))
return;
for (unsigned short whichItem = 1; whichItem <= numItems; ++whichItem) {
ClippingID clippingID;
ItemReference dragItem;
if (GetDragItemReferenceNumber (dragRef, whichItem, &dragItem))
return;
if (RememberDragItem (dragRef, dragItem, clippingID, dropLocation)) {
newClippingMade = true;
}
}
if (newClippingMade)
WakeUpProcess(&glob.myPSN);
}
static
void DiscardClippingWindow (WindowPtr win)
{
ClippingID id = GetWRefCon (win);
if (id && DeleteClippingFile (id) == noErr) {
DeleteClipping (id);
DisposeFloater (win);
} else
DisposeFloater (win);
}
static
void ClippingDisposeProc (WindowPtr win)
{
ClippingID id = GetWRefCon (win);
if (id)
DeleteClipping (id);
DisposeFloater (win);
}
static void MySetCursor (Cursor* cursor)
{
// Call SetCursor directly through jSetCursor, since someone's stupid patch does not allow
// SetCursor to operate properly. :-(
// Wish I knew why I was passing in 16, but the ROM does it. When in ROMe...
typedef pascal void (*jSetCrsrProc) (Point, short, void*, void*);
(*((jSetCrsrProc*) 0x00000818)) (cursor -> hotSpot, 16, &cursor -> data, &cursor -> mask);
}
static
void ClippingWindowMouseDown (WindowPtr win, EventRecord *theEvent)
{
GrafPtr oldPort;
GetPort (&oldPort);
SetPort (win);
gClickPoint = theEvent -> where;
GlobalToLocal (&gClickPoint);
SetPort (oldPort);
if (WaitMouseMoved (theEvent -> where)) {
ClippingID id = GetWRefCon (win);
ClippingRec clipping;
short whichClipping = FindClipping (id, clipping);
Boolean draggedToSelf = false;
if (whichClipping >= 0) {
DragReference dragRef;
OSErr error = ClippingFileToDragReference (id, dragRef, true);
if (error == noErr) {
RgnHandle rgn1 = NewRgn ();
RgnHandle rgn2 = NewRgn ();
CopyRgn (((WindowPeek)win) -> contRgn, rgn1);
CopyRgn (rgn1, rgn2);
InsetRgn (rgn2, 1, 1);
DiffRgn (rgn1, rgn2, rgn1);
gWindowBeingDragged = win;
MySetCursor (&qd.arrow);
error = TrackDrag (dragRef, theEvent, rgn1);
if (gWindowBeingDragged == nil)
draggedToSelf = true;
else
draggedToSelf = false;
gWindowBeingDragged = nil;
DisposeRgn (rgn1);
DisposeRgn (rgn2);
DisposeDrag (dragRef);
if (error == noErr && ((theEvent -> modifiers & optionKey) == 0) &&
!OptionKeyDown () && !draggedToSelf) {
DiscardClippingWindow (win);
}
}
}
}
}
static
void ClippingEventHandler (EventRecord *theEvent, WindowPtr win)
{
switch (theEvent -> what) {
case updateEvt :
GrafPtr oldPort;
long refCon;
ClippingRec clipping;
GetPort (&oldPort);
SetPort (win);
Rect r = win -> portRect;
InsetRect (&r, 6, 2);
BeginUpdate (win);
EraseRect (&win -> portRect);
if (FindClipping (GetWRefCon (win), clipping) >= 0) {
if (clipping.thumbnail)
clipping.thumbnail -> Draw (r);
}
EndUpdate (win);
break;
case mouseDown :
short partCode = theEvent -> message;
switch (partCode) {
case inContent :
ClippingWindowMouseDown (win, theEvent);
break;
case inDrag :
break;
}
break;
case keyDown :
case autoKey :
break;
}
}
WindowPtr CreateClippingWindow (ClippingID id, Rect& bounds, Boolean onLeft)
{
GrafPtr oldPort;
Handle wctb = GetResource ('wctb', 128 + (Random () & 0x7FFF) % 6);
WindowPtr win = NewFloater (nil, &bounds, "\p", true, onLeft ? kLeftWindowProc : kRightWindowProc, (WindowPtr) -1,
false, id, 0, ClippingEventHandler, ClippingDisposeProc);
if (!win)
return nil;
if (wctb)
SetWinColor (win, (WinCTab**)wctb);
ShowWindow (win);
UpdateFloater (win);
return win;
}
#if 0
void RepositionClipping (DragReference drag, WindowPtr w)
{
Point mouse, pinnedMouse;
OSErr error = GetDragMouse (drag, &mouse, &pinnedMouse);
if (!error) {
mouse.h -= gClickPoint.h;
mouse.v -= gClickPoint.v;
Boolean onLeft;
Rect bounds = w -> portRect;
CalcWindowPosition (mouse, bounds, 0, onLeft);
MoveWindow (w, bounds.left, bounds.top, false);
}
}
#endif
#endif